本篇的委託單的Contract會以股票做範例。期貨跟選擇權,下單方式跟股票相同,只要參考前一篇建立對應的Order內容即可。
若以虛擬環境及帳號,可正常建立委託單及其它操作,也可以看到成交資訊
但重新登入後,之前的trade都會被清除
api.place_order參數說明:
api.place_order(
contract: Contract,
order: Order,
timeout: int = 5000
)
在建立委託單之前,要先取得Contract物件及建立Order物件,完整範例如下:
from dotenv import load_dotenv
import os
import shioaji as sj
from shioaji.constant import Action, StockPriceType, TFTOrderType, TFTStockOrderLot #匯入下單常用常數
load_dotenv('D:\\python\\shioaji\\.env') #讀取.env中的環境變數
api = sj.Shioaji()
api.login(
person_id=os.getenv('YOUR_PERSON_ID'),
passwd=os.getenv('YOUR_PASSWORD')
)
#啟用電子憑證
result = api.activate_ca(
ca_path=os.getenv('YOUR_CA_PATH'),
ca_passwd=os.getenv('YOUR_CA_PASS'),
person_id=os.getenv('YOUR_PERSON_ID'),
)
contract = api.Contracts.Stocks['2890'] #取得Contract物件
order = api.Order( #建立order內容
price=13.8,
quantity=1,
action=Action.Buy,
price_type=StockPriceType.LMT,
order_type=TFTOrderType.ROD,
order_lot=TFTStockOrderLot.Common,
account=api.stock_account
)
trade = api.place_order(contract, order) #執行place_order並傳入contract及order建立委託單
print(trade) #將委託單內容輸出至console
若成功建立委託單,會回傳Trade物件,輸出至console後就會出現下列資訊:
contract=Stock(exchange=<Exchange.TSE: 'TSE'>, code='2890', symbol='TSE2890', name='永豐金', category='17', unit=1000, limit_up=15.2, limit_down=12.5, reference=13.85, update_date='2021/09/24', day_trade=<DayTrade.Yes: 'Yes'>)
order=Order(action=<Action.Buy: 'Buy'>, price=13.8, quantity=1, id='ca6171d5', seqno='092803', ordno='00000', account=Account(account_type=<AccountType.Stock: 'S'>, person_id='PAPIUSER06', broker_id='9A95', account_id='0506701', signed=True), price_type=<StockPriceType.LMT: 'LMT'>, order_type=<FuturesOrderType.ROD: 'ROD'>)
status=OrderStatus(id='ca6171d5', status=<Status.PendingSubmit: 'PendingSubmit'>, status_code='0', order_datetime=datetime.datetime(2021, 9, 26, 17, 54, 14), deals=[])
可以看到Trade物件的內容分為contract、order及status;contract及order的內容,就是剛才建立並傳入的內容,status就是這張委託單的狀態。
status有以下7種:
狀態 | 說明 |
---|---|
PendingSubmit | 傳送中 |
PreSubmitted | 預約單 |
Submitted | 傳送成功 |
Failed | 傳送失敗 |
Cancelled | 已取消 |
Filled | 全部成交 |
Filling | 部分成交 |
委託單建立後,會看到status是PendingSubmit,請先執行一次api.update_status(api.stock_account)更新股票帳戶的狀態,若委託成功,就可以看到trade中的status已變為Submitted。
若要修改委託單內容,可使用api.update_order()進行修改
api.update_order(
trade: Trade, #傳入原本的委託單
price: typing.Union[StrictInt, float] = None, #變更後的委託價格
qty: int = None, #qty指的是所要取消的委託數量
timeout: int = 5000
)
範例如下:
api.update_status(api.stock_account) #執行update_status更新股票帳戶的狀態
api.update_order(trade=trade, price=12, qty=2) #傳入所要修改的委託單,將委託價格更改為12,且委託數量取消2
api.update_status(api.stock_account) #再次執行update_status更新股票帳戶的狀態
print(trade.status.status.value) #將委託單的狀態值輸出至console
若修改成功,trade.status.status.value中的值就會變成'Submitted',並且在status中,可以看到多了cancel_quantity取消數量及modified_price修改價格兩個屬性值。
若要取消委託單,可使用api.cancel_order()進行取消
api.cancel_order(
trade: shioaji.order.Trade,
timeout: int = 5000
)
範例如下:
api.update_status(api.stock_account) #執行update_status更新股票帳戶的狀態
api.cancel_order(trade) #傳入所要取消的委託單
api.update_status(api.stock_account) #再次執行update_status更新股票帳戶的狀態
print(trade.status.status.value) #將委託單的狀態值輸出至console
若成功取消,trade.status.status.value中的值就會變成'Cancelled'
從Trade的status中,可以看此張委託單是否已成交,若委託單已成交,status中的值會是Filling部份成交或Filled全部成交,deal_quantity則為成交的數量,而deals中會顯示成交的價格、數量和時間。
Trade(contract=Stock(exchange=<Exchange.TSE: 'TSE'>, code='2890', symbol='TSE2890', name='永豐金', category='17', unit=1000, limit_up=15.3, limit_down=12.6, reference=13.95, update_date='2021/09/27', day_trade=<DayTrade.Yes: 'Yes'>), order=Order(action=<Action.Buy: 'Buy'>, price=13.8, quantity=1, id='0ab3dd4a', seqno='092823', ordno='WA027', account=Account(account_type=<AccountType.Stock: 'S'>, person_id='PAPIUSER06', broker_id='9A95', account_id='0506701', signed=True), price_type=<StockPriceType.LMT: 'LMT'>, order_type=<FuturesOrderType.ROD: 'ROD'>), status=OrderStatus(id='0ab3dd4a', status=<Status.Filled: 'Filled'>, status_code='00', order_datetime=datetime.datetime(2021, 9, 27, 10, 56, 37), modified_price=14.0, deal_quantity=1, deals=[Deal(seq='000928', price=14.0, quantity=1, ts=1632712382)]))